// src/services/kline-utils.service.ts
// 处理K线数据转换、更新和格式化的工具函数

import { FormattedKlineData } from './market-data.service';
// 导入类型
import { TAKlineData } from '../types/indicator.types';

export class KlineUtilsService {
  /**
   * 将格式化后的K线数据转换为技术分析所需格式
   * @param formattedKlines 格式化后的K线数据
   * @returns 转换后的技术分析格式K线数据
   */
  convertFormattedToTA(formattedKlines: any[]): TAKlineData[] {
    return formattedKlines.map(kline => ({
      timestamp: kline.timestamp,
      open: kline.open,
      high: kline.high,
      low: kline.low,
      close: kline.close,
      volume: kline.volume || kline.volumeCcy || 0
    }));
  }

  /**
   * 将WebSocket推送的K线数据转换为技术指标分析所需格式
   */
  convertWebSocketToTA(
    wsData: [string, string, string, string, string, string]
  ): TAKlineData {
    const [timestamp, open, high, low, close, confirm] = wsData;
    return {
      timestamp: parseInt(timestamp),
      open: parseFloat(open),
      high: parseFloat(high),
      low: parseFloat(low),
      close: parseFloat(close),
      volume: 0 // WebSocket数据中可能没有成交量信息
    };
  }

  /**
   * 更新K线数据数组，添加或更新单条K线
   */
  updateKlines(klines: TAKlineData[], newKline: TAKlineData, maxSize: number): TAKlineData[] {
    // 创建副本以避免修改原数组
    const updatedKlines = [...klines];

    // 查找是否已有此K线
    const existingIndex = updatedKlines.findIndex(k => {
      const kTs = typeof k.timestamp === 'string' ? parseInt(k.timestamp) : k.timestamp;
      const newTs = typeof newKline.timestamp === 'string' ? parseInt(newKline.timestamp) : newKline.timestamp;
      return kTs === newTs;
    });

    if (existingIndex !== -1) {
      // 更新现有K线
      updatedKlines[existingIndex] = newKline;
    } else {
      // 添加新K线
      updatedKlines.push(newKline);
      // 保持数组大小
      if (updatedKlines.length > maxSize) {
        updatedKlines.shift();
      }
    }

    // 确保按时间排序
    updatedKlines.sort((a, b) => {
      const aTs = typeof a.timestamp === 'string' ? parseInt(a.timestamp) : a.timestamp;
      const bTs = typeof b.timestamp === 'string' ? parseInt(b.timestamp) : b.timestamp;
      return aTs - bTs;
    });

    return updatedKlines;
  }

  /**
   * 从K线数据创建价格映射表
   */
  createPriceMap(klines: TAKlineData[]): Record<number, number> {
    return klines.reduce((map, kline) => {
      const timestamp = typeof kline.timestamp === 'string' ? parseInt(kline.timestamp) : kline.timestamp;
      map[timestamp] = kline.close;
      return map;
    }, {} as Record<number, number>);
  }

  /**
   * 将REST API K线周期转换为WebSocket订阅周期
   */
  convertToWebSocketPeriod(restApiPeriod: string): string {
    // 创建映射表
    const periodMap: Record<string, string> = {
      '1s': '1s',
      '1m': '1m',
      '3m': '3m',
      '5m': '5m',
      '15m': '15m',
      '30m': '30m',
      '1H': '1H',
      '2H': '2H',
      '4H': '4H',
      '6H': '6H',
      '12H': '12H',
      '1D': '1D',
      '1W': '1W'
    };

    return periodMap[restApiPeriod] || '1H';
  }
} 